#!/usr/bin/env  python
#coding : utf-8

import MySQLdb
import logger
import singleton
import MySQLdb.cursors 
import itertools
import sys
reload(sys)
sys.setdefaultencoding('utf8')


from singleton import Singleton
from logger import StaffLogger

class KeyNotFound(Exception): pass
class DbNotConnectException(Exception): pass
	

class Connection(object):
	def __init__(self, database, **config):
		if config.has_key('host'):
			self.host = config['host']
		else:
			raise KeyNotFound

		self.database = database

		args = dict(charset = 'utf8', db = database)
		if config.has_key('user'):
			args['user'] = config['user']	
		if config.has_key('password'):
			args['passwd'] = config['password']

		self.socket = None
		if config.has_key('host'):
			host = config['host']
		else:
			host = 'localhost'
		pair = host.split(':')
		if len(pair) == 2:
			args['host'] = pair[0]
			args['port'] = pair[1]
		else:
			args['host'] = host
			args['port'] = 3306
		self._db = None	
		self._db_args = args
		
		try:
			self.connect()
		except:
			Singleton.getInst(StaffLogger, log_name = 'debug.log').debug('cannt connect to database %s' % database)
			
	
	def __del__(self):
		self.close()

	def close(self):
		if getattr(self, '_db', None) is not None:
			self._db.close()
			self._db = None	

	def connect(self):
		self.close()
		self._db = MySQLdb.connect(**self._db_args)
		self._db.autocommit(True)

	def query(self, query, *param):
		cursor = self._cursor()
		self._excute(cursor, query, *param)
		column_names = [d[0] for d in cursor.description]
		return [dict(itertools.izip(column_names, row)) for row in cursor]
	
	def get(self, query, *param):
		rows = self.query(query, *param)
		if not rows:
			return None
		else:
			return rows[0]

	def modify(self, query, *param):
		cursor = self._cursor()
		r = self._excute(cursor, query, param)	
		return r
	
	def excute(self, query, *param):
		cursor = self._cursor()
		try:
			self._excute(cursor, query, *param)		
			return cursor.lastrowid
		finally:
			cursor.close()

	def _excute(self, cursor, query, *param):
		try:
			cursor.execute("SET NAMES 'utf8'") 
			cursor.execute("SET CHARACTER_SET_CLIENT=utf8") 
			cursor.execute("SET CHARACTER_SET_RESULTS=utf8") 
			return cursor.execute(query)
		except:
			import traceback
			error_str = traceback.format_exc()
			print error_str

	def _cursor(self):
		if self._db is None:
			self.connect()
		return self._db.cursor()
		
		
class DataBase(object):
	def __init__(self, **config):
		self._connections_config = {}
		self._connections_config.update(config)	
		self._connections = {}

	def __getattr__(self, dbname):
		return self.get_db(dbname) 
		
	def get_db(self, dbname):
		if dbname is None:
			return None
		if self._connections.has_key(dbname):
			return self._connections[dbname]	
		else: 
			print self._connections_config
			conn = Connection(dbname, **self._connections_config)
			self._connections[dbname] = conn
			return conn
		return None
		

global_db = DataBase(host = 'localhost', user = 'root', password = 'hustyouku')

if __name__ == '__main__':
	db = DataBase(host = 'localhost', user = 'root', password = 'hustyouku')
	conn = db.get_db('homework')
	conn.excute('set character_set_results=utf8;')
	conn.excute('set character_set_server=utf8;')
	conn.excute('set character_set_connection=utf8;')
	conn.excute('set character_set_client=utf8;')
	x = conn.query('select * from staff_info;')
	print x
	print x[0]['name']
